package com.movie.controller;

import com.movie.utils.JwtUtil;
import com.movie.dto.ApiResponse;
import com.movie.dto.UserDTO;
import com.movie.entity.User;
import com.movie.service.UserService;
import lombok.RequiredArgsConstructor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestHeader;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.time.LocalDateTime;
import java.util.HashMap;
import java.util.Map;

@RestController
@RequestMapping("/auth")
@RequiredArgsConstructor
public class AuthController {

    private final JwtUtil jwtUtil;
    private final UserService userService;
    private final PasswordEncoder passwordEncoder;

    @PostMapping("/login")
    public ApiResponse<Map<String, Object>> login(@RequestBody LoginRequest loginRequest) {
        try {
            // 查询数据库验证用户
            UserDTO user = userService.findByUsername(loginRequest.getUsername());

            // 验证密码
            if (!passwordEncoder.matches(loginRequest.getPassword(), user.getPassword())) {
                return ApiResponse.error("用户名或密码错误");
            }

            // 检查用户状态
            if (!user.getStatus()) {
                return ApiResponse.error("用户已被禁用，请联系管理员");
            }

            // 生成JWT令牌
            String token = jwtUtil.generateToken(user.getUsername());

            Map<String, Object> userData = new HashMap<>();
            userData.put("token", token);
            userData.put("username", user.getUsername());
            userData.put("userId", user.getId());
            userData.put("email", user.getEmail());
            userData.put("createdAt", user.getCreatedAt());
            if (user.getVipLevel() != null) {
                userData.put("vipLevel", user.getVipLevel());
            }
            // 更新最后登录时间
            userService.updateLastLogin(user.getId());
            userData.put("lastLogin", LocalDateTime.now());

            return ApiResponse.success("登录成功", userData);
        } catch (RuntimeException e) {
            return ApiResponse.error("用户名或密码错误");
        }
    }

    // 注册接口
    @PostMapping("/register")
    public ApiResponse<Map<String, Object>> register(@RequestBody RegisterRequest registerRequest) {
        try {
            // 验证输入
            if (registerRequest.getUsername() == null || registerRequest.getUsername().trim().isEmpty()) {
                return ApiResponse.error("用户名不能为空");
            }

            if (registerRequest.getPassword() == null || registerRequest.getPassword().length() < 6) {
                return ApiResponse.error("密码长度不能少于6位");
            }

            if (registerRequest.getEmail() == null || !registerRequest.getEmail().contains("@")) {
                return ApiResponse.error("邮箱格式不正确");
            }

            // 创建用户DTO
            UserDTO userDTO = new UserDTO();
            userDTO.setUsername(registerRequest.getUsername());
            userDTO.setPassword(registerRequest.getPassword());
            userDTO.setEmail(registerRequest.getEmail());
            // 默认角色为编辑（通过权限服务分配角色）
            // 这里不设置roles，由权限服务处理角色分配

            // 调用UserService创建用户
            UserDTO createdUser = userService.create(userDTO);

            // 生成JWT令牌
            String token = jwtUtil.generateToken(createdUser.getUsername());

            Map<String, Object> userData = new HashMap<>();
            userData.put("token", token);
            userData.put("username", createdUser.getUsername());
            userData.put("userId", createdUser.getId());
            userData.put("email", createdUser.getEmail());


            return ApiResponse.success("注册成功", userData);
        } catch (RuntimeException e) {
            return ApiResponse.error(e.getMessage());
        }
    }

    // 获取用户信息接口
    @GetMapping("/profile")
    public ApiResponse<Map<String, Object>> getProfile(@RequestHeader(value = "Authorization", required = false) String authHeader) {
        try {
            // 验证Authorization头
            if (authHeader == null || !authHeader.startsWith("Bearer ")) {
                return ApiResponse.error(401, "未授权访问");
            }

            // 提取token
            String token = authHeader.substring(7);

            // 验证token
            if (!jwtUtil.validateToken(token)) {
                return ApiResponse.error(401, "令牌无效或已过期");
            }

            // 从token中解析用户名
            String username = jwtUtil.getUsernameFromToken(token);

            // 查询数据库获取用户信息
            UserDTO user = userService.findByUsername(username);

            Map<String, Object> userData = new HashMap<>();
            userData.put("username", user.getUsername());
            userData.put("userId", user.getId());
            userData.put("email", user.getEmail());
            userData.put("status", user.getStatus());
            userData.put("lastLogin", user.getLastLogin());
            userData.put("createdAt", user.getCreatedAt());
            if (user.getVipLevel() != null) {
                userData.put("vipLevel", user.getVipLevel());
            }
            return ApiResponse.success(userData);
        } catch (RuntimeException e) {
            return ApiResponse.error("获取用户信息失败");
        }
    }

    // 退出登录接口
    @PostMapping("/logout")
    public ApiResponse<String> logout(@RequestHeader(value = "Authorization", required = false) String authHeader) {
        try {
            // 验证Authorization头
            if (authHeader == null || !authHeader.startsWith("Bearer ")) {
                return ApiResponse.error(401, "未授权访问");
            }
            // 提取token
            String token = authHeader.substring(7);
            // 验证token有效性
            if (!jwtUtil.validateToken(token)) {
                return ApiResponse.error(401, "令牌无效或已过期");
            }
            // 无服务端状态则由客户端丢弃令牌；如有黑名单机制可在此将token加入黑名单
            return ApiResponse.success("退出登录成功");
        } catch (RuntimeException e) {
            return ApiResponse.error("退出登录失败");
        }
    }

    // 重置密码接口
    @PostMapping("/reset-password")
    public ApiResponse<String> resetPassword(@RequestBody ResetPasswordRequest resetRequest) {
        try {
            // 验证邮箱格式
            if (resetRequest.getEmail() == null || !resetRequest.getEmail().contains("@")) {
                return ApiResponse.error("邮箱格式不正确");
            }

            // 查询用户是否存在
            UserDTO user = userService.findByEmail(resetRequest.getEmail());
            if (user == null) {
                return ApiResponse.error("该邮箱未注册");
            }

            // 生成重置令牌并发送邮件（这里简化处理）
            String resetToken = jwtUtil.generateResetToken(user.getEmail());

            // 在实际项目中，这里应该发送包含重置链接的邮件
            // mailService.sendResetPasswordEmail(user.getEmail(), resetToken);

            return ApiResponse.success("密码重置链接已发送到您的邮箱");
        } catch (RuntimeException e) {
            return ApiResponse.error("重置密码失败，请稍后重试");
        }
    }

    // 请求类定义
    public static class LoginRequest {
        private String username;
        private String password;

        public String getUsername() {
            return username;
        }

        public void setUsername(String username) {
            this.username = username;
        }

        public String getPassword() {
            return password;
        }

        public void setPassword(String password) {
            this.password = password;
        }
    }

    public static class RegisterRequest {
        private String username;
        private String password;
        private String email;

        public String getUsername() {
            return username;
        }

        public void setUsername(String username) {
            this.username = username;
        }

        public String getPassword() {
            return password;
        }

        public void setPassword(String password) {
            this.password = password;
        }

        public String getEmail() {
            return email;
        }

        public void setEmail(String email) {
            this.email = email;
        }
    }


    public static class ResetPasswordRequest {
        private String email;

        public String getEmail() {
            return email;
        }

        public void setEmail(String email) {
            this.email = email;
        }
    }
}